using System;
using System.Collections.Generic;
using System.Text;
using Ent.Voice.Show;
using Ent.Voice.Organisation;
using System.Data;
using Ent.SqlDB;
namespace Ent.Voice.Nomination
{
    public enum EntryStatus { Live, Suspend }
    public enum OrderBy { Title, Entered, Votes, Points, None }
    public enum EntryFilter { Event = 0, User = 1 }
    public class Entry
    {
        public int Id;
        public int EventId;
        //Inherited from Event -> not to be added in DB
        public EventAccess Accessibility = EventAccess.Private;
        public string AccessCode;
        public string OrganiserId;
        public string EventTitle;
        public EntryStatus Status;
        //end Inherited
        public string Title;
        public string Description;
        public DateTime Date;
        public File Upload;
        public User Nominee;
        public int Votes;
        public int Points;
        public int Attended;
        public int Views;
        public List<KeyValuePair<string, string>> Comments = new List<KeyValuePair<string, string>>();
        public static VoteCriteria GetVoteCriteria(int entryId)
        {
            int eventId = GetEntry(entryId, null).EventId;
            return Event.GetVoteCriteria(eventId);
        }
        public static Entry GetEntry(int entryid)
        {
            return GetEntry(entryid, "-1");
        }
        public static Entry GetEntry(int entryid, string expCode)
        {
            Dictionary<string, object> pars = new Dictionary<string, object>();
            pars.Add("Id", entryid);
            pars.Add("expCode", expCode);
            pars.Add("incView", 1);
            Dictionary<string, VSqlDbType> outpars = new Dictionary<string, VSqlDbType>();
            outpars.Add("Comments", new VSqlDbType(SqlDbType.VarChar, 500));
            ReaderResponse rr = Execute.SPReader("Voice_GetEntryDetails", pars, outpars);
            if (rr.Table != null && rr.Table.Rows.Count > 0)
            {
                Entry en = SetEntry(rr.Table.Rows[0]);
                en.Comments = Global.ParseKeyValueText(Convert.ToString(rr.OutParams["Comments"]));
                return en;
            }
            else
                return null;
        }
        public static void ToggleStatus(int entryid)
        {
            Dictionary<string, object> pars = new Dictionary<string, object>();
            pars.Add("EntryId", entryid);
            NonQueryResponse rr = Execute.SPNonQuery("Voice_ToggleEntryStatus", pars, null);
        }
        public static Entry[] GetEventEntries(string EventId, string key, int startIndex, int rowcount, string orderby, bool includeSuspended, string viewId, ref int total)
        {
            return Search(EntryFilter.Event, EventId, key, startIndex, rowcount, orderby, includeSuspended, viewId, ref total);
        }
        public static Entry[] GetUserEntries(string UserId, string key, int startIndex, int rowcount, string orderby, bool includeSuspended, string viewId, ref int total)
        {
            return Search(EntryFilter.User, UserId, key, startIndex, rowcount, orderby, includeSuspended, viewId, ref total);
        }
        public static Entry[] Search(EntryFilter filterType, string Id, string key, int startIndex, int rowcount, string orderby, bool includeSuspended, string viewId, ref int total)
        {
            //Count Votes Id Name Winners
            Dictionary<string, object> pars = new Dictionary<string, object>();
            pars.Add("type", (int)filterType);
            pars.Add("Id", Id);
            pars.Add("key", key);
            pars.Add("startIndex", startIndex);
            pars.Add("rowCount", rowcount);
            pars.Add("orderBy", orderby);
            pars.Add("viewUserId", viewId);
            if (includeSuspended)
                pars.Add("includeSuspended", 1);
            Dictionary<string, VSqlDbType> outpars = new Dictionary<string, VSqlDbType>();
            outpars.Add("count", new VSqlDbType(SqlDbType.Int, -1));
            ReaderResponse rr = Execute.SPReader("Voice_SearchEntry", pars, outpars);
            total = Convert.ToInt32(rr.OutParams["count"]);
            if (rr.Table != null && rr.Table.Rows.Count > 0)
            {
                Entry[] retValue = new Entry[rr.Table.Rows.Count];
                for (int i = 0; i < rr.Table.Rows.Count; i++)
                {
                    retValue.SetValue(SetEntry(rr.Table.Rows[i]), i);
                }
                return retValue;
            }
            else
                return null;
        }
        private static Entry SetEntry(DataRow dr)
        {
            Entry retValue = new Entry();
            if (dr.Table.Columns.Contains("Id"))
                retValue.Id = dr["Id"] != null ? Convert.ToInt32(dr["Id"]) : 0;
            if (dr.Table.Columns.Contains("Event"))
                retValue.EventId = dr["Event"] != null ? Convert.ToInt32(dr["Event"]) : 0;
            if (dr.Table.Columns.Contains("Title"))
                retValue.Title = dr["Title"].ToString();
            if (dr.Table.Columns.Contains("Description"))
                retValue.Description = dr["Description"].ToString();
            if (dr.Table.Columns.Contains("Entered"))
                retValue.Date = dr["Entered"] != null ? Convert.ToDateTime(dr["Entered"]) : DateTime.MinValue;
            retValue.Upload = new File();
            if (dr.Table.Columns.Contains("Location"))
                retValue.Upload.Location = dr["Location"].ToString();
            if (dr.Table.Columns.Contains("Text"))
                retValue.Upload.Text = dr["Text"].ToString();
            if (dr.Table.Columns.Contains("FileType"))
                retValue.Upload.Type = File.GetFileType(dr["FileType"].ToString());
            if (dr.Table.Columns.Contains("Width"))
                retValue.Upload.Width = dr["Width"] != null ? Convert.ToInt32(dr["Width"]) : 0;
            if (dr.Table.Columns.Contains("Height"))
                retValue.Upload.Height = dr["Height"] != null ? Convert.ToInt32(dr["Height"]) : 0;
            retValue.Nominee = new User();
            if (dr.Table.Columns.Contains("Nominee"))
                retValue.Nominee.UserID = dr["Nominee"].ToString();
            if (dr.Table.Columns.Contains("Fname"))
                retValue.Nominee.FName = dr["Fname"].ToString();
            if (dr.Table.Columns.Contains("Lname"))
                retValue.Nominee.LName = dr["Lname"].ToString();
            if (dr.Table.Columns.Contains("Votes"))
                retValue.Votes = dr["Votes"] != null ? Convert.ToInt32(dr["Votes"]) : 0;
            if (dr.Table.Columns.Contains("Points"))
                retValue.Points = dr["Points"] != null ? Convert.ToInt32(dr["Points"]) : 0; 
            if (dr.Table.Columns.Contains("Attended"))
                retValue.Attended = dr["Attended"] != null ? Convert.ToInt32(dr["Attended"]) : 0; 
            if (dr.Table.Columns.Contains("Views"))
                retValue.Views = dr["Views"] != null ? Convert.ToInt32(dr["Views"]) : 0;
            if (dr.Table.Columns.Contains("EventAccess"))
                retValue.Accessibility = dr["EventAccess"] != System.DBNull.Value ? (EventAccess)Enum.Parse(typeof(EventAccess), Convert.ToString(dr["EventAccess"]), true) : EventAccess.Private;
            if (dr.Table.Columns.Contains("EventAccessCode"))
                retValue.AccessCode = dr["EventAccessCode"].ToString();
            if (dr.Table.Columns.Contains("Organiser"))
                retValue.OrganiserId = dr["Organiser"].ToString();
            if (dr.Table.Columns.Contains("EventTitle"))
                retValue.EventTitle = dr["EventTitle"].ToString();
            if (dr.Table.Columns.Contains("Status"))
                retValue.Status = dr["Status"] != System.DBNull.Value ? (EntryStatus)Enum.Parse(typeof(EntryStatus), Convert.ToString(dr["Status"]), true) : EntryStatus.Live;
            
            return retValue;
        }

        private static OrderBy GetRandomOrder()
        {
            Random ran = new Random();
            switch (ran.Next(1, 5))
            {
                case 1:
                    return OrderBy.Entered;
                case 2:
                    return OrderBy.Points;
                case 3:
                    return OrderBy.Title;
                case 4:
                default:
                    return OrderBy.Votes;
            }
        }
        public static OrderBy GetOrderBy(int order)
        {
            switch (order)
            {
                case 1:
                    return OrderBy.Entered;
                case 2:
                    return OrderBy.Points;
                case 3:
                    return OrderBy.Title;
                case 4:
                    return OrderBy.Votes;
                default:
                    return GetRandomOrder();
            }
        }
        public static int GetOrderBy(OrderBy orderby)
        {
            switch (orderby)
            {
                case OrderBy.Entered:
                    return 1;
                case OrderBy.Points:
                    return 2;
                case OrderBy.Title:
                    return 3;
                case OrderBy.Votes:
                    return 4;
                default:
                    return GetOrderBy(GetOrderBy(-1));
            }
        }
    }
}
